package com.zzedu.controller;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.zzedu.common.annotation.Log;
import com.zzedu.common.core.controller.BaseController;
import com.zzedu.common.core.domain.AjaxResult;
import com.zzedu.common.core.domain.entity.SysUser;
import com.zzedu.common.core.page.TableDataInfo;
import com.zzedu.common.enums.BusinessStatus;
import com.zzedu.common.enums.BusinessType;
import com.zzedu.common.enums.OperatorType;
import com.zzedu.common.utils.SecurityUtils;
import com.zzedu.common.utils.ServletUtils;
import com.zzedu.common.utils.StringUtils;
import com.zzedu.common.utils.file.FileUtils;
import com.zzedu.common.utils.poi.ExcelUtil;
import com.zzedu.common.utils.uuid.IdUtils;
import com.zzedu.domain.ZzUploadFile;
import com.zzedu.dto.ZzUploadFileDTO;
import com.zzedu.enmuns.FileRelationTypeEnum;
import com.zzedu.framework.manager.AsyncManager;
import com.zzedu.framework.manager.factory.AsyncFactory;
import com.zzedu.integration.oss.IOssClientService;
import com.zzedu.integration.oss.dto.FileInfoDTO;
import com.zzedu.integration.oss.dto.OssFileResult;
import com.zzedu.params.UploadFileParams;
import com.zzedu.service.IZzUploadFileService;
import com.zzedu.system.domain.SysOperationLog;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.util.StopWatch;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;

import java.util.List;

/**
 * 资源管理Controller
 *
 * @author Mr.Wang
 * @date 2025-01-30
 */
@RestController
@RequestMapping("/fileresource/file")
public class ZzUploadFileController extends BaseController {
    private static final Logger log = LoggerFactory.getLogger(ZzUploadFileController.class);
    @Autowired
    private IOssClientService ossClientService;


    @Autowired
    private IZzUploadFileService zzUploadFileService;


    /**
     * 上传文件
     *
     * @param uploadFileParams
     * @return
     */
    @RequestMapping("/fileUpload")
    public AjaxResult fileUpload(@Validated UploadFileParams uploadFileParams) {
        FileRelationTypeEnum fileRelationTypeEnum = uploadFileParams.getRelationType();
        StopWatch stopWatch = new StopWatch();
        stopWatch.start();
        SysUser currentUser = SecurityUtils.getSysUser();
        SysOperationLog operLog = new SysOperationLog();
        operLog.setStatus(BusinessStatus.FAIL.ordinal());
        try {
            // 设置action动作
            operLog.setBusinessType(BusinessType.OTHER.ordinal());
            // 设置标题
            operLog.setTitle("管理平台上传文件");
            // 设置操作人类别
            operLog.setOperatorType(OperatorType.MOBILE.ordinal());
            String ip = SecurityUtils.getIp();
            operLog.setOperIp(ip);
            // 设置请求方式
            operLog.setRequestMethod(ServletUtils.getRequest().getMethod());
            operLog.setOperUrl(ServletUtils.getRequest().getRequestURI());
            if (currentUser != null) {
                operLog.setOperName(currentUser.getUserName());
                if (StringUtils.isNotNull(currentUser.getDept())
                        && StringUtils.isNotEmpty(currentUser.getDept().getDeptName())) {
                    operLog.setDeptName(currentUser.getDept().getDeptName());
                }
                operLog.setCreateBy(currentUser.getId());
            }
            operLog.setMethod("com.zzedu.controller.ZzUploadFileController.fileUpload()");
            MultipartFile file = uploadFileParams.getFile();
            JSONObject openParams = new JSONObject();
            openParams.put("fileName",uploadFileParams.getFile().getName());
            operLog.setOperParam(openParams.toJSONString());
            OssFileResult<FileInfoDTO>  fileUploadResult = ossClientService.uploadFile(file.getBytes(), fileRelationTypeEnum.getOssPath(),file.getOriginalFilename(), IdUtils.fastSimpleUUID());
            if (fileUploadResult.isSuccess()) {
                operLog.setStatus(BusinessStatus.SUCCESS.ordinal());
                FileInfoDTO fileInfoDTO = fileUploadResult.getData();
                operLog.setJsonResult(JSON.toJSONString(fileInfoDTO));
                ZzUploadFile uploadFile = new ZzUploadFile();
                uploadFile.setRelationType(fileRelationTypeEnum.getCode());
                uploadFile.setUrl(fileInfoDTO.getUrl());
                uploadFile.setOldFileName(fileInfoDTO.getOriginalFilename());
                uploadFile.setFileName(FileUtils.getName(fileInfoDTO.getNewFileName()));
                uploadFile.setRelationId(uploadFileParams.getRelationId());
                uploadFile.setFileExt(fileInfoDTO.getFileSuffix());
                uploadFile.setSourceModel(fileRelationTypeEnum.getCode());
                uploadFile.setSize(fileInfoDTO.getSize());
                uploadFile.setSortNum(uploadFile.getId());
                zzUploadFileService.save(uploadFile);
                uploadFile.setUrl(ossClientService.convertURL(uploadFile.getUrl()));
                uploadFile.setSortNum(uploadFile.getId());
                return AjaxResult.success(uploadFile);
            } else {
                operLog.setJsonResult(JSON.toJSONString(fileUploadResult));
            }
        } catch (Exception e) {
            log.error("上传文件失败,详细:{}", e.getMessage());
            operLog.setJsonResult(new JSONObject() {{
                put("msg", "上传文件失败,详细:" + e.getMessage());
            }}.toJSONString());
        } finally {
            stopWatch.stop();
            operLog.setCostTime(stopWatch.getTotalTimeMillis());
            AsyncFactory.recordOper(operLog);
        }
        return AjaxResult.error("上传文件失败,请稍后重试");
    }

    /**
     * 查询资源管理列表
     */
    @PreAuthorize("@permission.hasAnyPermissions('fileresource:file:query')")
    @RequestMapping("/list")
    public TableDataInfo list(@RequestBody ZzUploadFileDTO zzUploadFile) {
        return getDataTable(zzUploadFileService.page(zzUploadFile.getPageDTO(), zzUploadFileService.buildQuery(zzUploadFile)));
    }

    /**
     * 导出资源管理列表
     */
    @PreAuthorize("@permission.hasAnyPermissions('fileresource:file:export')")
    @Log(title = "资源管理", businessType = BusinessType.EXPORT)
    @RequestMapping("/export")
    public void export(ZzUploadFileDTO zzUploadFile) {
        List<ZzUploadFile> list = zzUploadFileService.list(zzUploadFileService.buildQuery(zzUploadFile));
        ExcelUtil<ZzUploadFile> util = new ExcelUtil<ZzUploadFile>(ZzUploadFile.class);
        util.exportExcel(ServletUtils.getResponse(), list, "资源管理数据");
    }


    /**
     * 新增保存资源管理
     */
    @PreAuthorize("@permission.hasAnyPermissions('fileresource:file:add')")
    @Log(title = "资源管理", businessType = BusinessType.INSERT)
    @RequestMapping("/add")
    public AjaxResult addSave(@Validated @RequestBody ZzUploadFile zzUploadFile) {
        return toAjax(zzUploadFileService.save(zzUploadFile));
    }


    /**
     * 获取资源管理详细信息
     */
    @PreAuthorize("@permission.hasAnyPermissions('fileresource:file:query')")
    @RequestMapping(value = "/{id}")
    public AjaxResult getInfo(@PathVariable("id") Long id) {
        return success(zzUploadFileService.getById(id));
    }


    /**
     * 修改保存资源管理
     */
    @PreAuthorize("@permission.hasAnyPermissions('fileresource:file:edit')")
    @Log(title = "资源管理", businessType = BusinessType.UPDATE)
    @RequestMapping("/edit")
    public AjaxResult editSave(@Validated @RequestBody ZzUploadFile zzUploadFile) {
        return toAjax(zzUploadFileService.updateById(zzUploadFile));
    }

    /**
     * 删除资源管理
     */
    @PreAuthorize("@permission.hasAnyPermissions('fileresource:file:remove')")
    @Log(title = "资源管理", businessType = BusinessType.DELETE)
    @RequestMapping("/remove/{ids}")
    public AjaxResult remove(@PathVariable List<Long> ids) {
        return toAjax(zzUploadFileService.removeBatchByIds(ids));
    }
}
